#include "mainwindow.h"
#include "ui_mainwindow.h"
#include "chartwindow.h"
#include "multichartwindow.h"
#include <QDateTime>
#include <QGridLayout>
#include <QStringConverter>
#include <QFileDialog>
#include <QMessageBox>
#include <QVector>

MainWindow::MainWindow(QWidget *parent)
    : QMainWindow(parent)
    , ui(new Ui::MainWindow)
{
    ui->setupUi(this);
    initUI();
    initSerial();
    on_refreshButton_clicked();

    // 初始化maxPoints变量（图表显示的采样点数量）
    maxPoints = 2000;
    
    // 初始化dataLimit变量（数据采集的上限）
    dataLimit = 1000000;
    
    // 初始化数据计数器，必须显式初始化为0以避免随机值
    dataCounter = 0;
    
    // 初始化数据采样和保存相关变量
    isSavingData = false;
    dataFile = nullptr;
    dataStream = nullptr;
    
    // 初始化串口控制变量
    isClosing = false;
    
    // 初始化时间轴相关变量
    // 注意：firstDataReceived变量已移除，数据显示逻辑已转移到各图表窗口
    
    // 初始化状态栏定时器
    statusTimer = new QTimer(this);
    connect(statusTimer, &QTimer::timeout, this, &MainWindow::updateStatus);
    statusTimer->start(1000); // 每秒更新一次
    
    // 初始化状态栏时钟
    clockLabel = new QLabel(this);
    clockLabel->setAlignment(Qt::AlignRight);
    
    // 初始化时间轴自动滚动相关变量
    timeAxisTimer = new QTimer(this);
    connect(timeAxisTimer, &QTimer::timeout, this, &MainWindow::updateTimeAxis);
    lastDataUpdateTime = 0;
    timeAxisUpdateInterval = 100; // 默认100ms更新一次
    timeAxisAutoScroll = true;
    
    // 初始化暂停状态变量
    isPaused = false;
    
    // 初始化采样参数输入框的值
    ui->sampleSizeEdit->setText(QString::number(maxPoints));
    ui->dataLimitEdit->setText(QString::number(dataLimit));
    ui->statusBar->addPermanentWidget(clockLabel); // 添加到状态栏右侧（永久显示）
    
    // 连接采样参数输入框的信号和槽
    connect(ui->sampleSizeEdit, &QLineEdit::editingFinished, this, [=]() {
        bool ok;
        qint64 value = ui->sampleSizeEdit->text().toLongLong(&ok);
        if (ok && value >= 50) { // 验证输入在有效范围内（下限为50，上限理论上无限制）
            ui->sampleSizeLabel->setText(QString::number(value));
            
            // 更新主窗口的maxPoints变量
            maxPoints = value;
            
            // 由于我们已经移除了主界面图表，所以不需要更新主界面图表
            // 主窗口只负责配置和数据收集
            
            // 更新扩展图表窗口的采样点数量
            if (chartWindow) {
                chartWindow->setMaxPoints(value);
            }
            
            // 更新六个数据通道窗口的采样点数量
            if (dataWindow1) dataWindow1->setMaxPoints(value);
            if (dataWindow2) dataWindow2->setMaxPoints(value);
            if (dataWindow3) dataWindow3->setMaxPoints(value);
            if (dataWindow4) dataWindow4->setMaxPoints(value);
            if (dataWindow5) dataWindow5->setMaxPoints(value);
            if (dataWindow6) dataWindow6->setMaxPoints(value);
            
            // 更新多图表整合窗口的采样点数量
            if (multiChartWindow) {
                multiChartWindow->setMaxPoints(value);
            }
        } else {
            // 输入无效，恢复之前的值
            ui->sampleSizeEdit->setText(QString::number(maxPoints));
            QMessageBox::warning(this, "输入错误", "采样点数量必须大于等于50");
        }
    });
    
    // 连接数据采集上限输入框的信号和槽
    connect(ui->dataLimitEdit, &QLineEdit::editingFinished, this, [=]() {
        bool ok;
        qint64 value = ui->dataLimitEdit->text().toLongLong(&ok);
        if (ok && value >= 100000 && value <= 10000000) { // 验证输入在有效范围内（10万-1千万）
            // 更新数据采集上限变量
            dataLimit = value;
            
            // 如果当前数据计数器已经超过新的上限，重置计数器
            if (dataCounter >= dataLimit) {
                dataCounter = 0;
            }
            
            ui->dataLimitLabel->setText(QString::number(value));
        } else {
            // 输入无效，恢复之前的值
            ui->dataLimitEdit->setText(QString::number(dataLimit));
            QMessageBox::warning(this, "输入错误", "数据采集上限必须在100000到10000000之间");
        }
    });
    
    connect(ui->sampleTimeEdit, &QLineEdit::editingFinished, this, [=]() {
        bool ok;
        int value = ui->sampleTimeEdit->text().toInt(&ok);
        if (ok && value >= 1 && value <= 10000) { // 验证输入在有效范围内
            ui->sampleTimeLabel->setText(QString::number(value) + " ms");
            // 这里可以添加调整采样时间的逻辑
        } else {
            // 输入无效，恢复之前的值
            ui->sampleTimeEdit->setText("5");
            QMessageBox::warning(this, "输入错误", "采样时间必须在1-10000 ms之间");
        }
    });
    
    // 初始化图表窗口指针
    chartWindow = nullptr;
    dataWindow1 = nullptr;
    dataWindow2 = nullptr;
    dataWindow3 = nullptr;
    dataWindow4 = nullptr;
    dataWindow5 = nullptr;
    dataWindow6 = nullptr;
    
    // 初始化多图表整合窗口指针
    multiChartWindow = nullptr;
    
    // 添加菜单选项
    QMenu *viewMenu = menuBar()->addMenu("视图");
    
    // 添加显示扩展图表的菜单项
    QAction *showChartAction = new QAction("扩展图表", this);
    connect(showChartAction, &QAction::triggered, this, &MainWindow::on_actionShowChart_triggered);
    viewMenu->addAction(showChartAction);
    
    // 添加显示多图表整合窗口的菜单项
    QAction *actionShowMultiChart = new QAction("多图表整合窗口", this);
    connect(actionShowMultiChart, &QAction::triggered, this, [this]() {
        if (!multiChartWindow) {
            multiChartWindow = new MultiChartWindow(this);
            multiChartWindow->setMaxPoints(maxPoints);
            multiChartWindow->setSampleTime(ui->sampleTimeEdit->text().toInt());
            
            // 连接重置数据计数器的信号
            connect(multiChartWindow, &MultiChartWindow::resetDataCounter, this, &MainWindow::resetDataCounter);
            
            // 当窗口关闭时释放资源
            connect(multiChartWindow, &QMainWindow::destroyed, [this]() {
                multiChartWindow = nullptr;
            });
            
            // 连接参数更改信号
            connect(multiChartWindow, &MultiChartWindow::sampleSizeChanged, this, [this](qint64 newSize) {
                // 更新主窗口的maxPoints变量
                maxPoints = newSize;
                ui->sampleSizeEdit->setText(QString::number(newSize));
                ui->sampleSizeLabel->setText(QString::number(newSize));
                
                // 由于我们已经移除了主界面图表，所以不需要更新主界面图表
                
                // 更新其他所有窗口的采样点数量
                if (chartWindow) chartWindow->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
                if (dataWindow1) dataWindow1->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
                if (dataWindow2) dataWindow2->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
                if (dataWindow3) dataWindow3->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
                if (dataWindow4) dataWindow4->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
                if (dataWindow5) dataWindow5->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
                if (dataWindow6) dataWindow6->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
            });
            
            connect(multiChartWindow, &MultiChartWindow::sampleTimeChanged, this, [this](int newTime) {
                // 更新主窗口的采样时间
                ui->sampleTimeEdit->setText(QString::number(newTime));
                ui->sampleTimeLabel->setText(QString::number(newTime) + " ms");
                
                // 更新其他所有窗口的采样时间
                if (chartWindow) chartWindow->updateControlsSilently(maxPoints, newTime);
                if (dataWindow1) dataWindow1->updateControlsSilently(maxPoints, newTime);
                if (dataWindow2) dataWindow2->updateControlsSilently(maxPoints, newTime);
                if (dataWindow3) dataWindow3->updateControlsSilently(maxPoints, newTime);
                if (dataWindow4) dataWindow4->updateControlsSilently(maxPoints, newTime);
                if (dataWindow5) dataWindow5->updateControlsSilently(maxPoints, newTime);
                if (dataWindow6) dataWindow6->updateControlsSilently(maxPoints, newTime);
            });
        }
        
        multiChartWindow->show();
        multiChartWindow->raise();
        multiChartWindow->activateWindow();
    });
    viewMenu->addAction(actionShowMultiChart);
    
    // 添加分隔线
    viewMenu->addSeparator();
    
    // 添加六个数据窗口的菜单选项
    for (int i = 0; i < 6; ++i) {
        QString actionName = QString("显示数据通道 %1").arg(i + 1);
        QAction *channelAction = new QAction(actionName, this);
        channelAction->setObjectName(QString("actionShowChannel%1").arg(i + 1));
        
        // 使用lambda表达式连接信号到槽函数，传递通道索引
        connect(channelAction, &QAction::triggered, [this, i]() {
            showDataWindow(i + 1); // 通道编号从1开始
        });
        
        viewMenu->addAction(channelAction);
    }
    
    // 程序启动时自动创建并显示多图表整合窗口
    if (!multiChartWindow) {
        multiChartWindow = new MultiChartWindow(this);
        multiChartWindow->setMaxPoints(maxPoints);
        multiChartWindow->setSampleTime(ui->sampleTimeEdit->text().toInt());
        
        // 连接重置数据计数器的信号
        connect(multiChartWindow, &MultiChartWindow::resetDataCounter, this, &MainWindow::resetDataCounter);
        
        // 当窗口关闭时释放资源
        connect(multiChartWindow, &QMainWindow::destroyed, [this]() {
            multiChartWindow = nullptr;
        });
        
        // 连接参数更改信号
        connect(multiChartWindow, &MultiChartWindow::sampleSizeChanged, this, [this](qint64 newSize) {
            // 更新主窗口的maxPoints变量
            maxPoints = newSize;
            ui->sampleSizeEdit->setText(QString::number(newSize));
            ui->sampleSizeLabel->setText(QString::number(newSize));
        });
        
        connect(multiChartWindow, &MultiChartWindow::sampleTimeChanged, this, [this](int newTime) {
            // 更新主窗口的采样时间
            ui->sampleTimeEdit->setText(QString::number(newTime));
            ui->sampleTimeLabel->setText(QString::number(newTime) + " ms");
        });
    }
    
    multiChartWindow->show();
    multiChartWindow->raise();
    multiChartWindow->activateWindow();
}

MainWindow::~MainWindow()
{
    savePortSettings();
    delete ui;
    delete serial;
    delete statusTimer;
    
    // 由于我们已经移除了主界面图表，所以不需要释放相关资源
    // 数据直接传递给扩展图表窗口进行显示
}
void MainWindow::initUI()
{
    // 重新组织UI布局：只显示配置信息，图表全部移至拓展窗口
    
    // 1. 先从当前布局中移除所有子部件
    QVBoxLayout *oldLayout = qobject_cast<QVBoxLayout*>(ui->centralWidget->layout());
    if (oldLayout) {
        // 存储所有子部件
        QList<QWidget*> widgets;
        while (oldLayout->count() > 0) {
            QLayoutItem *item = oldLayout->takeAt(0);
            if (item->widget()) {
                widgets.append(item->widget());
                item->widget()->setParent(nullptr);
            }
            delete item;
        }
        delete oldLayout;
    }
    
    // 2. 创建新的水平主布局
    QHBoxLayout *mainLayout = new QHBoxLayout(ui->centralWidget);
    mainLayout->setSpacing(10);
    mainLayout->setContentsMargins(10, 10, 10, 10);
    
    // 3. 创建右侧容器用于放置配置和数据区域
    QWidget *configPanel = new QWidget(this);
    QVBoxLayout *configLayout = new QVBoxLayout(configPanel);
    configPanel->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
    configPanel->setMinimumWidth(800); // 扩大配置面板宽度
    
    // 将原有部件添加到右侧面板
    configLayout->addWidget(ui->serialSettingsGroupBox);
    configLayout->addWidget(ui->receiveGroupBox);
    configLayout->addWidget(ui->sendGroupBox);
    configLayout->setStretch(1, 1); // 让接收区拉伸
    
    // 5. 将配置面板添加到主布局
    mainLayout->addWidget(configPanel);
    mainLayout->setStretch(0, 1); // 配置面板占据全部空间

    // 初始化数据计数器
    dataCounter = 0;
    
    // 创建数据管理设置区域
    QGroupBox *dataManagementGroupBox = new QGroupBox("数据管理", this);
    QVBoxLayout *dataManagementLayout = new QVBoxLayout(dataManagementGroupBox);
    
    // 采样方式选择
    QHBoxLayout *samplingLayout = new QHBoxLayout();
    samplingLayout->addWidget(new QLabel("采样方式:"));
    dataSamplingComboBox = new QComboBox();
    dataSamplingComboBox->addItems({"全部接收", "时间采样", "点数采样"});
    samplingLayout->addWidget(dataSamplingComboBox);
    dataManagementLayout->addLayout(samplingLayout);
    
    // 采样率设置
    QHBoxLayout *samplingRateLayout = new QHBoxLayout();
    samplingRateLayout->addWidget(new QLabel("采样率(ms/点):"));
    samplingRateSpinBox = new QSpinBox();
    samplingRateSpinBox->setRange(1, 1000);
    samplingRateSpinBox->setValue(5); // 设置默认采样间隔为5ms
    samplingRateLayout->addWidget(samplingRateSpinBox);
    dataManagementLayout->addLayout(samplingRateLayout);
    
    // 自适应采样开关
    adaptiveSamplingCheckBox = new QCheckBox("启用自适应采样", this);
    adaptiveSamplingCheckBox->setChecked(false); // 默认禁用
    dataManagementLayout->addWidget(adaptiveSamplingCheckBox);
    
    // 数据保存按钮
    saveDataButton = new QPushButton("开始保存数据", this);
    connect(saveDataButton, &QPushButton::clicked, this, &MainWindow::on_saveDataButton_clicked);
    dataManagementLayout->addWidget(saveDataButton);
    
    // 将数据管理设置区域添加到右侧配置面板
    configLayout->addWidget(dataManagementGroupBox);
    // 由于我们已经移除了主界面图表，所以不需要初始化相关组件

    // 设置波特率选项
    ui->baudRateComboBox->addItems({"9600", "19200", "38400", "57600", "115200", "230400", "460800", "921600"});
    ui->baudRateComboBox->setCurrentText("115200");

    // 设置数据位选项
    ui->dataBitsComboBox->addItems({"5", "6", "7", "8"});
    ui->dataBitsComboBox->setCurrentText("8");

    // 设置校验位选项
    ui->parityComboBox->addItems({"None", "Even", "Odd", "Space", "Mark"});
    ui->parityComboBox->setCurrentIndex(0);

    // 设置停止位选项
    ui->stopBitsComboBox->addItems({"1", "1.5", "2"});
    ui->stopBitsComboBox->setCurrentText("1");

    // 设置流控制选项
    ui->flowControlComboBox->addItems({"None", "RTS/CTS", "XON/XOFF"});
    ui->flowControlComboBox->setCurrentIndex(0);

    // 禁用发送按钮
    ui->sendButton->setEnabled(false);

    // 设置接收区为只读
    ui->receiveTextEdit->setReadOnly(true);

    // 动态添加周期发送相关控件到发送区布局
    QHBoxLayout *periodicLayout = new QHBoxLayout();
    periodicSendCheckBox = new QCheckBox("周期发送(ms)", this);
    periodicSendSpinBox = new QLineEdit("25", this);
    periodicSendSpinBox->setMaximumWidth(60);
    periodicSendSpinBox->setValidator(new QIntValidator(1, 10000, this));
    
    periodicLayout->addWidget(periodicSendCheckBox);
    periodicLayout->addWidget(periodicSendSpinBox);
    
    // 获取发送区的布局并添加新控件
    QVBoxLayout *sendLayout = qobject_cast<QVBoxLayout*>(ui->sendGroupBox->layout());
    if (sendLayout) {
        // 在发送按钮行之前添加周期发送控件行
        QLayoutItem *item = sendLayout->takeAt(sendLayout->count() - 1);
        sendLayout->addLayout(periodicLayout);
        sendLayout->addItem(item);
    }

    // 连接周期发送复选框的信号
    connect(periodicSendCheckBox, &QCheckBox::checkStateChanged, this, [this](Qt::CheckState state) {
        on_periodicSendCheckBox_stateChanged(static_cast<int>(state));
    });

    // 加载上次保存的设置
    loadPortSettings();
    
    // 初始化周期发送定时器
    periodicSendTimer = new QTimer(this);
    connect(periodicSendTimer, &QTimer::timeout, this, &MainWindow::sendPeriodicData);
    
    // 使用UI文件中定义的数据采集参数设置区域
    configLayout->addWidget(ui->samplingParamsGroupBox);
    
    // 采样参数控件的信号连接已在构造函数中定义，无需重复连接
}

void MainWindow::initSerial()
{
    serial = new QSerialPort(this);
    
    // 保存连接的信号槽连接，以便后续可以断开
    readyReadConnection = connect(serial, &QSerialPort::readyRead, this, &MainWindow::readData);
    
    connect(serial, &QSerialPort::errorOccurred, [this](QSerialPort::SerialPortError error) {
        if (error != QSerialPort::NoError) {
            QString errorMsg = "串口错误: " + serial->errorString();
            ui->statusBar->showMessage(errorMsg);
            
            // 避免在关闭过程中再次触发关闭
            if (!isClosing) {
                // 记录错误并尝试关闭串口
                qDebug() << errorMsg;
                
                // 使用QMetaObject::invokeMethod确保在主线程中执行关闭操作
                QMetaObject::invokeMethod(this, "safeCloseSerial", Qt::QueuedConnection);
            }
        }
    });
}

void MainWindow::safeCloseSerial()
{
    // 强制设置关闭标志，确保状态一致性
    isClosing = true;
    
    if (serial->isOpen()) {
        // 禁用按钮防止重复点击
        ui->openButton->setEnabled(false);
        ui->statusBar->showMessage("正在关闭串口...");
        
        // 停止所有可能正在进行的操作
        if (periodicSendTimer->isActive()) {
            periodicSendTimer->stop();
            periodicSendCheckBox->setChecked(false);
        }
        
        // 断开串口信号连接，防止在关闭过程中触发新的读取
        if (readyReadConnection) {
            disconnect(readyReadConnection);
            readyReadConnection = QMetaObject::Connection();
        }
        
        // 停止时间轴更新定时器
        if (timeAxisTimer->isActive()) {
            timeAxisTimer->stop();
        }
        
        // 重置暂停状态
        if (isPaused) {
            isPaused = false;
            ui->pauseButton->setText("暂停");
        }
        
        // 清空串口缓冲区
        serial->clear();
        
        // 关闭串口
        serial->close();
        
        // 添加小延迟确保串口完全关闭
        QThread::msleep(200);
        
        // 检查串口是否真正关闭，如果没有关闭成功则尝试多次关闭
        int retryCount = 0;
        const int maxRetries = 3;
        while (serial->isOpen() && retryCount < maxRetries) {
            retryCount++;
            ui->statusBar->showMessage(QString("尝试重新关闭串口 (%1/%2)...").arg(retryCount).arg(maxRetries));
            
            // 清除错误状态
            serial->clearError();
            
            // 再次尝试关闭
            serial->close();
            
            // 等待更久一些
            QThread::msleep(150);
        }
        
        // 最终检查关闭状态
        // 最终检查关闭状态，并设置相应的UI
        if (!serial->isOpen()) {
            ui->openButton->setText("打开串口");
            ui->sendButton->setEnabled(false);
            ui->portComboBox->setEnabled(true);
            ui->baudRateComboBox->setEnabled(true);
            ui->dataBitsComboBox->setEnabled(true);
            ui->parityComboBox->setEnabled(true);
            ui->stopBitsComboBox->setEnabled(true);
            ui->flowControlComboBox->setEnabled(true);
            ui->statusBar->showMessage("串口已关闭");
        } else {
            // 关闭失败，显示详细错误信息
            ui->statusBar->showMessage("关闭串口失败: " + serial->errorString() + ", 请再次尝试关闭");
            
            // 根据实际串口状态设置按钮文本
            ui->openButton->setText("关闭串口");
        }
        
        // 重新连接信号，为下次打开做准备或继续处理事件
        readyReadConnection = connect(serial, &QSerialPort::readyRead, this, &MainWindow::readData);
        
        // 恢复按钮状态
        ui->openButton->setEnabled(true);
        
    }
    
    // 无论关闭操作是否成功，确保重置关闭标志
    isClosing = false;
}

// 重置数据计数器的槽函数
void MainWindow::resetDataCounter()
{
    dataCounter = 0;
    qDebug() << "数据计数器已重置为0";
}
void MainWindow::on_openButton_clicked()
{
    // 检查串口的实际状态，不依赖于UI状态
    if (serial->isOpen()) {
        // 确保按钮状态一致
        ui->openButton->setText("关闭串口");
        ui->openButton->setEnabled(true);
        
        // 调用安全关闭方法
        safeCloseSerial();
    } else {
        // 确保按钮状态一致
        ui->openButton->setText("打开串口");
        ui->openButton->setEnabled(true);
        // 打开串口
        if (ui->portComboBox->currentText().isEmpty() || ui->portComboBox->currentText() == "无可用串口") {
            ui->statusBar->showMessage("请选择有效的串口");
            return;
        }

        // 保持按钮状态一致，不要禁用按钮
        // 防止重复点击通过线程安全的方式处理，而不是禁用按钮
        ui->statusBar->showMessage("正在打开串口...");

        // 使用单独的线程来执行串口打开操作，避免UI卡顿
        QThread* openThread = new QThread(this);
        QObject::connect(openThread, &QThread::started, [this, openThread]() {
            // 保存当前选中的串口参数
            QString portName = ui->portComboBox->currentText().split(" - ").first();
            int baudRate = ui->baudRateComboBox->currentText().toInt();
            int dataBits = ui->dataBitsComboBox->currentText().toInt();
            int parity = ui->parityComboBox->currentIndex();
            QString stopBits = ui->stopBitsComboBox->currentText();
            int flowControl = ui->flowControlComboBox->currentIndex();

            // 创建临时串口对象进行打开操作
            QSerialPort tempSerial;
            tempSerial.setPortName(portName);
            tempSerial.setBaudRate(baudRate);

            // 设置数据位
            switch (dataBits) {
            case 5:
                tempSerial.setDataBits(QSerialPort::Data5);
                break;
            case 6:
                tempSerial.setDataBits(QSerialPort::Data6);
                break;
            case 7:
                tempSerial.setDataBits(QSerialPort::Data7);
                break;
            case 8:
            default:
                tempSerial.setDataBits(QSerialPort::Data8);
                break;
            }

            // 设置校验位
            switch (parity) {
            case 0:
                tempSerial.setParity(QSerialPort::NoParity);
                break;
            case 1:
                tempSerial.setParity(QSerialPort::EvenParity);
                break;
            case 2:
                tempSerial.setParity(QSerialPort::OddParity);
                break;
            case 3:
                tempSerial.setParity(QSerialPort::SpaceParity);
                break;
            case 4:
                tempSerial.setParity(QSerialPort::MarkParity);
                break;
            default:
                tempSerial.setParity(QSerialPort::NoParity);
                break;
            }

            // 设置停止位
            if (stopBits == "1") {
                tempSerial.setStopBits(QSerialPort::OneStop);
            } else if (stopBits == "1.5") {
                tempSerial.setStopBits(QSerialPort::OneAndHalfStop);
            } else if (stopBits == "2") {
                tempSerial.setStopBits(QSerialPort::TwoStop);
            } else {
                tempSerial.setStopBits(QSerialPort::OneStop);
            }

            // 设置流控制
            switch (flowControl) {
            case 0:
                tempSerial.setFlowControl(QSerialPort::NoFlowControl);
                break;
            case 1:
                tempSerial.setFlowControl(QSerialPort::HardwareControl);
                break;
            case 2:
                tempSerial.setFlowControl(QSerialPort::SoftwareControl);
                break;
            default:
                tempSerial.setFlowControl(QSerialPort::NoFlowControl);
                break;
            }

            bool success = false;
            QString errorMsg;
            
            // QSerialPort没有setTimeout方法，移除这行代码
            success = tempSerial.open(QIODevice::ReadWrite);
            
            if (success) {
                // 打开成功，关闭临时串口，并在主线程中设置和打开主串口
                tempSerial.close();
            } else {
                errorMsg = tempSerial.errorString();
            }

            // 将结果发送回主线程处理
            QMetaObject::invokeMethod(this, "handleSerialOpenResult", 
                                      Qt::QueuedConnection, 
                                      Q_ARG(bool, success), 
                                      Q_ARG(QString, errorMsg));
            
            openThread->quit();
        });
        
        QObject::connect(openThread, &QThread::finished, openThread, &QObject::deleteLater);
        openThread->start();
    }
}

// 处理串口打开结果的槽函数
void MainWindow::handleSerialOpenResult(bool success, const QString &errorMsg)
{
    if (success) {
        // 重新应用所有设置并打开主串口
        serial->setPortName(ui->portComboBox->currentText().split(" - ").first());
        serial->setBaudRate(ui->baudRateComboBox->currentText().toInt());

        // 设置数据位
        switch (ui->dataBitsComboBox->currentText().toInt()) {
        case 5:
            serial->setDataBits(QSerialPort::Data5);
            break;
        case 6:
            serial->setDataBits(QSerialPort::Data6);
            break;
        case 7:
            serial->setDataBits(QSerialPort::Data7);
            break;
        case 8:
            serial->setDataBits(QSerialPort::Data8);
            break;
        default:
            serial->setDataBits(QSerialPort::Data8);
            break;
        }

        // 设置校验位
        switch (ui->parityComboBox->currentIndex()) {
        case 0:
            serial->setParity(QSerialPort::NoParity);
            break;
        case 1:
            serial->setParity(QSerialPort::EvenParity);
            break;
        case 2:
            serial->setParity(QSerialPort::OddParity);
            break;
        case 3:
            serial->setParity(QSerialPort::SpaceParity);
            break;
        case 4:
            serial->setParity(QSerialPort::MarkParity);
            break;
        default:
            serial->setParity(QSerialPort::NoParity);
            break;
        }

        // 设置停止位
        if (ui->stopBitsComboBox->currentText() == "1") {
            serial->setStopBits(QSerialPort::OneStop);
        } else if (ui->stopBitsComboBox->currentText() == "1.5") {
            serial->setStopBits(QSerialPort::OneAndHalfStop);
        } else if (ui->stopBitsComboBox->currentText() == "2") {
            serial->setStopBits(QSerialPort::TwoStop);
        } else {
            serial->setStopBits(QSerialPort::OneStop);
        }

        // 设置流控制
        switch (ui->flowControlComboBox->currentIndex()) {
        case 0:
            serial->setFlowControl(QSerialPort::NoFlowControl);
            break;
        case 1:
            serial->setFlowControl(QSerialPort::HardwareControl);
            break;
        case 2:
            serial->setFlowControl(QSerialPort::SoftwareControl);
            break;
        default:
            serial->setFlowControl(QSerialPort::NoFlowControl);
            break;
        }

        // 再次尝试打开主串口
        if (serial->open(QIODevice::ReadWrite)) {
            ui->openButton->setText("关闭串口");
            ui->sendButton->setEnabled(true);
            ui->portComboBox->setEnabled(false);
            ui->baudRateComboBox->setEnabled(false);
            ui->dataBitsComboBox->setEnabled(false);
            ui->parityComboBox->setEnabled(false);
            ui->stopBitsComboBox->setEnabled(false);
            ui->flowControlComboBox->setEnabled(false);
            ui->statusBar->showMessage("串口已打开: " + ui->portComboBox->currentText());
            savePortSettings();
            
            // 启动时间轴更新定时器，确保即使没有新数据也能让时间轴继续滚动
            timeAxisTimer->start(timeAxisUpdateInterval);
        } else {
            ui->statusBar->showMessage("无法打开串口: " + serial->errorString());
            ui->openButton->setText("打开串口");
            ui->openButton->setEnabled(true);
        }
    } else {
        ui->statusBar->showMessage("无法打开串口: " + errorMsg);
        ui->openButton->setText("打开串口");
        ui->openButton->setEnabled(true);
    }
}

void MainWindow::on_sendButton_clicked()
{
    if (!serial->isOpen()) {
        ui->statusBar->showMessage("串口未打开");
        return;
    }

    QString sendData = ui->sendTextEdit->toPlainText();
    if (sendData.isEmpty()) {
        return;
    }

    // 根据发送格式选项准备数据
    QByteArray dataToSend;
    if (ui->asciiRadioButton->isChecked()) {
        // ASCII模式
        dataToSend = sendData.toLocal8Bit();
        
        // 如果勾选了"发送新行"，添加换行符
        if (ui->newLineCheckBox->isChecked()) {
            dataToSend += "\r\n";
        }
    } else if (ui->hexRadioButton->isChecked()) {
        // HEX模式
        // 移除所有非十六进制字符
        QString hexData = sendData.remove(QRegularExpression("[^0-9A-Fa-f]"));
        
        // 确保字符数为偶数
        if (hexData.length() % 2 != 0) {
            hexData.append('0'); // 在末尾添加0
        }
        
        // 转换为二进制数据
        for (int i = 0; i < hexData.length(); i += 2) {
            QString byteString = hexData.mid(i, 2);
            bool ok;
            char byte = static_cast<char>(byteString.toUInt(&ok, 16));
            if (ok) {
                dataToSend.append(byte);
            }
        }
    }

    qint64 bytesWritten = serial->write(dataToSend);
    if (bytesWritten == -1) {
        ui->statusBar->showMessage("发送失败: " + serial->errorString());
    } else if (bytesWritten != dataToSend.size()) {
        ui->statusBar->showMessage("发送部分数据: " + QString::number(bytesWritten) + " / " + QString::number(dataToSend.size()));
    } else {
        ui->statusBar->showMessage("发送成功: " + QString::number(bytesWritten) + " 字节");
    }
}

void MainWindow::on_clearButton_clicked()
{
    ui->receiveTextEdit->clear();
}

void MainWindow::sendPeriodicData()
{
    if (!serial->isOpen()) {
        ui->statusBar->showMessage("串口未打开");
        return;
    }

    QString sendData = ui->sendTextEdit->toPlainText();
    if (sendData.isEmpty()) {
        return;
    }

    // 根据发送格式选项准备数据
    QByteArray dataToSend;
    if (ui->asciiRadioButton->isChecked()) {
        // ASCII模式
        dataToSend = sendData.toLocal8Bit();
        
        // 如果勾选了"发送新行"，添加换行符
        if (ui->newLineCheckBox->isChecked()) {
            dataToSend += "\r\n";
        }
    } else if (ui->hexRadioButton->isChecked()) {
        // HEX模式
        // 移除所有非十六进制字符
        QString hexData = sendData.remove(QRegularExpression("[^0-9A-Fa-f]"));
        
        // 确保字符数为偶数
        if (hexData.length() % 2 != 0) {
            hexData.append('0'); // 在末尾添加0
        }
        
        // 转换为二进制数据
        for (int i = 0; i < hexData.length(); i += 2) {
            QString byteString = hexData.mid(i, 2);
            bool ok;
            char byte = static_cast<char>(byteString.toUInt(&ok, 16));
            if (ok) {
                dataToSend.append(byte);
            }
        }
    }

    qint64 bytesWritten = serial->write(dataToSend);
    if (bytesWritten == -1) {
        ui->statusBar->showMessage("发送失败: " + serial->errorString());
    } else if (bytesWritten != dataToSend.size()) {
        ui->statusBar->showMessage("发送部分数据: " + QString::number(bytesWritten) + " / " + QString::number(dataToSend.size()));
    } else {
        ui->statusBar->showMessage("发送成功: " + QString::number(bytesWritten) + " 字节");
    }
}

void MainWindow::on_periodicSendCheckBox_stateChanged(int arg1)
{
    if (arg1 == Qt::Checked) {
        // 开始周期发送
        bool ok;
        int interval = periodicSendSpinBox->text().toInt(&ok);
        if (ok && interval > 0) {
            periodicSendTimer->start(interval);
            ui->statusBar->showMessage(QString("已开始周期发送，间隔 %1 ms").arg(interval));
        } else {
            ui->statusBar->showMessage("周期发送间隔无效");
            periodicSendCheckBox->setChecked(false);
        }
    } else {
        // 停止周期发送
        periodicSendTimer->stop();
        ui->statusBar->showMessage("已停止周期发送");
    }
}

void MainWindow::on_refreshButton_clicked()
{
    // 检查串口是否已连接
    bool wasOpen = serial->isOpen();
    QString currentPortName;
    
    // 如果已连接，保存当前端口名称
    if (wasOpen) {
        currentPortName = serial->portName();
        ui->statusBar->showMessage("刷新串口列表中...");
        
        // 临时禁用刷新按钮，防止重复点击
        ui->refreshButton->setEnabled(false);
    }
    
    ui->portComboBox->clear();

    // 获取所有可用串口
    foreach (const QSerialPortInfo &info, QSerialPortInfo::availablePorts()) {
        ui->portComboBox->addItem(info.portName() + " - " + info.description());
        
        // 如果是当前已连接的端口，选中它
        if (wasOpen && info.portName() == currentPortName) {
            ui->portComboBox->setCurrentText(info.portName() + " - " + info.description());
        }
    }

    // 统一管理按钮状态，确保在任何情况下都正确设置
    if (ui->portComboBox->count() == 0) {
        ui->portComboBox->addItem("无可用串口");
        ui->openButton->setEnabled(false);
    } else {
        if (wasOpen) {
            // 串口已打开状态
            ui->openButton->setText("关闭串口");
            ui->openButton->setEnabled(true);
            ui->portComboBox->setEnabled(false);
        } else {
            // 未连接状态
            ui->openButton->setText("打开串口");
            ui->openButton->setEnabled(true);
        }
    }
    
    // 恢复按钮状态和状态栏消息
    if (wasOpen) {
        ui->refreshButton->setEnabled(true);
        ui->statusBar->showMessage("串口列表已刷新");
    }
}

// 自适应采样相关的常量定义
const double ADAPTIVE_THRESHOLD_HIGH = 10.0; // 高变化率阈值
const double ADAPTIVE_THRESHOLD_LOW = 1.0;   // 低变化率阈值
const int MIN_SAMPLING_RATE = 1;             // 最小采样率
const int MAX_SAMPLING_RATE = 100;           // 最大采样率
const int ADAPTIVE_ADJUST_STEP = 1;          // 采样率调整步长

void MainWindow::readData()
{
    QByteArray data = serial->readAll();
    if (!data.isEmpty()) {
        // 更新上次数据更新时间
        lastDataUpdateTime = QDateTime::currentMSecsSinceEpoch();
        
        // 如果处于暂停状态，只更新时间戳，不处理数据
        if (isPaused) {
            return;
        }
        
        // 如果勾选了"显示时间戳"，添加时间戳
        if (ui->timestampCheckBox->isChecked()) {
            QDateTime currentDateTime = QDateTime::currentDateTime();
            QString timestamp = currentDateTime.toString("yyyy-MM-dd HH:mm:ss.zzz") + ": ";
            ui->receiveTextEdit->insertPlainText(timestamp);
        }

        // 根据显示格式选项显示数据
        if (ui->asciiRadioButton->isChecked()) {
            ui->receiveTextEdit->insertPlainText(QString(data));

            // 尝试解析ASCII数据并添加到图表
            QString dataStr = QString(data).trimmed();
            // 简单的解析逻辑：假设数据是以空格或换行分隔的数字
            QStringList dataList = dataStr.split(QRegularExpression("[\\s,;]+"), Qt::SkipEmptyParts);
            
            // 数据计数器，用于轮询分配到不同通道
            static int channelCounter = 0;
            
            // 采样相关变量
            static QDateTime lastSampleTime;
            QDateTime currentTime = QDateTime::currentDateTime();
            
            // 自适应采样相关变量
            static QVector<double> lastValues(6, 0);  // 记录每个通道的上一个值
            static QVector<double> valueChanges(6, 0); // 记录每个通道的值变化
            static QVector<int> adaptationCounters(6, 0); // 记录每个通道的适应计数器
            static const int ADAPTATION_INTERVAL = 50; // 每隔多少个数据点进行一次适应调整
            
            // 存储各通道的最新值，用于数据保存
            static QVector<double> latestValues(6, 0);
            
            // 采样相关变量
            static int sampleCounter = 0;
            
            foreach (QString str, dataList) {
                bool ok;
                double value = str.toDouble(&ok);
                if (ok) {
                    // 过滤异常大的数值，避免图表显示错误
                    if (value > 1000000000.0 || value < -1000000000.0) {
                        // 跳过过大或过小的数值
                        continue;
                    }
                    // 轮询将数据分配到六个通道
                    int channelIndex = channelCounter % 6;
                    
                    // 保存最新值
                    latestValues[channelIndex] = value;
                    
                    // 根据采样方式决定是否添加数据点到图表
                    bool shouldAddPoint = true;
                    
                    // 计算当前值与上一个值的变化
                    double change = qAbs(value - lastValues[channelIndex]);
                    lastValues[channelIndex] = value;
                    
                    // 累加变化量，用于后续的自适应调整
                    valueChanges[channelIndex] += change;
                    adaptationCounters[channelIndex]++;
                    
                    // 每隔一定数量的数据点进行一次自适应调整
                    if (adaptationCounters[channelIndex] >= ADAPTATION_INTERVAL) {
                        double avgChange = valueChanges[channelIndex] / adaptationCounters[channelIndex];
                        
                        // 只有当启用了自适应采样时，才进行调整
                        if (adaptiveSamplingCheckBox->isChecked()) {
                            // 根据平均变化率调整采样率
                            // 注意：这里只是简单演示，实际应用中可能需要根据具体需求调整算法
                            if (avgChange > ADAPTIVE_THRESHOLD_HIGH) {
                                // 数据变化较快，减小采样率（提高采样频率）
                                int newRate = samplingRateSpinBox->value() - ADAPTIVE_ADJUST_STEP;
                                samplingRateSpinBox->setValue(qMax(newRate, MIN_SAMPLING_RATE));
                            } else if (avgChange < ADAPTIVE_THRESHOLD_LOW) {
                                // 数据变化较慢，增大采样率（降低采样频率）
                                int newRate = samplingRateSpinBox->value() + ADAPTIVE_ADJUST_STEP;
                                samplingRateSpinBox->setValue(qMin(newRate, MAX_SAMPLING_RATE));
                            }
                        }
                        
                        // 重置计数器和变化量
                        valueChanges[channelIndex] = 0;
                        adaptationCounters[channelIndex] = 0;
                    }
                    
                    // "时间采样"模式
                    if (dataSamplingComboBox->currentIndex() == 1) {
                        // 首次运行或时间间隔超过采样率时添加数据点
                        if (lastSampleTime.isNull() || lastSampleTime.msecsTo(currentTime) >= samplingRateSpinBox->value()) {
                            lastSampleTime = currentTime;
                        } else {
                            shouldAddPoint = false;
                        }
                    }
                    // "点数采样"模式
                    else if (dataSamplingComboBox->currentIndex() == 2) {
                        // 每n个点采样一次
                        if (sampleCounter % samplingRateSpinBox->value() == 0) {
                            sampleCounter = 0;
                        } else {
                            shouldAddPoint = false;
                        }
                        sampleCounter++;
                    }
                    
                    // 使用实际计数器作为X轴坐标，确保值持续递增
                    qint64 actualX = dataCounter;
                        
                    // 如果需要添加数据点
                    if (shouldAddPoint) {
                        // 添加数据到多图表整合窗口（如果已创建），使用实际递增的X值
                        if (multiChartWindow) {
                            multiChartWindow->addDataPoint(channelIndex, actualX, value);
                        }

                        // 同时添加数据到扩展图表窗口（如果已创建），使用实际递增的X值
                        if (chartWindow) {
                            chartWindow->addDataPoint(actualX, value);
                        }

                        // 轮询将数据分配到六个通道窗口，使用实际递增的X值
                        switch (channelIndex) {
                        case 0: 
                            if (dataWindow1) dataWindow1->addDataPoint(actualX, value); 
                            break;
                        case 1: 
                            if (dataWindow2) dataWindow2->addDataPoint(actualX, value); 
                            break;
                        case 2: 
                            if (dataWindow3) dataWindow3->addDataPoint(actualX, value); 
                            break;
                        case 3: 
                            if (dataWindow4) dataWindow4->addDataPoint(actualX, value); 
                            break;
                        case 4: 
                            if (dataWindow5) dataWindow5->addDataPoint(actualX, value); 
                            break;
                        case 5: 
                            if (dataWindow6) dataWindow6->addDataPoint(actualX, value); 
                            break;
                        }
                    }
                    
                    // 递增数据计数器（无论是否添加数据点）
                    dataCounter++;
                    
                    // 限制dataCounter的最大值，防止溢出
                    // 使用dataLimit变量控制数据采集上限，不影响图表显示
                    if (dataCounter > dataLimit) {
                        dataCounter = 0; // 重置计数器
                    }
                    
                    // 递增通道计数器
                    channelCounter++;
                }
            }
            
            // 如果正在保存数据，写入CSV文件
            if (isSavingData && dataStream) {
                QString timestamp = QDateTime::currentDateTime().toString("yyyy-MM-dd HH:mm:ss.zzz");
                *dataStream << timestamp;
                
                // 写入各通道的最新值
                for (int i = 0; i < 6; i++) {
                    *dataStream << "," << latestValues[i];
                }
                
                *dataStream << "\n";
                dataStream->flush(); // 确保数据立即写入文件
            }
        } else if (ui->hexRadioButton->isChecked()) {
#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0)
            QString hexData = data.toHex().toUpper();
            // 添加空格分隔
            hexData = hexData.replace(QRegularExpression("(..)"), "\\1 ").trimmed();
#else
            QString hexData = data.toHex(' ').toUpper();
#endif
            ui->receiveTextEdit->insertPlainText(hexData + " ");
        }

        // 自动滚动到底部
        ui->receiveTextEdit->moveCursor(QTextCursor::End);
    }
}

void MainWindow::updateStatus()
{
    // 更新状态栏时钟
    QDateTime currentDateTime = QDateTime::currentDateTime();
    QString timeString = currentDateTime.toString("yyyy-MM-dd HH:mm:ss");
    clockLabel->setText(timeString);
    
    if (serial->isOpen()) {
        // 显示串口状态
        ui->statusBar->showMessage("串口已打开: " + ui->portComboBox->currentText() + " | 接收: " + QString::number(serial->bytesAvailable()) + " 字节");
    }
}

void MainWindow::loadPortSettings()
{
    // 在实际应用中，可以从配置文件加载设置
    // 这里简单实现，使用默认值
}

void MainWindow::savePortSettings()
{
    // 在实际应用中，可以保存设置到配置文件
    // 这里简单实现，不做实际保存
}

void MainWindow::on_actionShowChart_triggered()
{
    // 如果图表窗口不存在，则创建它
    if (!chartWindow) {
            chartWindow = new ChartWindow(this);
            
            // 连接重置数据计数器的信号
            connect(chartWindow, &ChartWindow::resetDataCounter, this, &MainWindow::resetDataCounter);
            
            // 设置窗口标题
            chartWindow->setWindowTitle("扩展数据可视化");
        
        // 设置最大数据点数量和采样时间
        chartWindow->setMaxPoints(maxPoints);
        chartWindow->setSampleTime(ui->sampleTimeEdit->text().toInt());
        
        // 由于我们已经移除了主界面图表，所以不需要从主界面同步数据
        // 新窗口将从创建后开始接收新的数据点
        
        // 当窗口关闭时释放资源
        connect(chartWindow, &QMainWindow::destroyed, [this]() {
            chartWindow = nullptr;
        });
        
        // 连接参数更改信号
            connect(chartWindow, &ChartWindow::sampleSizeChanged, this, [this](qint64 newSize) {
                // 更新主窗口的maxPoints变量
                maxPoints = newSize;
                ui->sampleSizeEdit->setText(QString::number(newSize));
                ui->sampleSizeLabel->setText(QString::number(newSize));
                
                // 由于我们已经移除了主界面图表，所以不需要更新主界面图表
                
                // 更新其他所有窗口的采样点数量
                if (dataWindow1 && dataWindow1 != chartWindow) dataWindow1->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
                if (dataWindow2 && dataWindow2 != chartWindow) dataWindow2->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
                if (dataWindow3 && dataWindow3 != chartWindow) dataWindow3->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
                if (dataWindow4 && dataWindow4 != chartWindow) dataWindow4->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
                if (dataWindow5 && dataWindow5 != chartWindow) dataWindow5->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
                if (dataWindow6 && dataWindow6 != chartWindow) dataWindow6->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
                if (multiChartWindow) multiChartWindow->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
            });
        
        connect(chartWindow, &ChartWindow::sampleTimeChanged, this, [this](int newTime) {
            // 更新主窗口的采样时间
            ui->sampleTimeEdit->setText(QString::number(newTime));
            ui->sampleTimeLabel->setText(QString::number(newTime) + " ms");
            
            // 更新其他所有窗口的采样时间
            if (dataWindow1 && dataWindow1 != chartWindow) dataWindow1->updateControlsSilently(maxPoints, newTime);
            if (dataWindow2 && dataWindow2 != chartWindow) dataWindow2->updateControlsSilently(maxPoints, newTime);
            if (dataWindow3 && dataWindow3 != chartWindow) dataWindow3->updateControlsSilently(maxPoints, newTime);
            if (dataWindow4 && dataWindow4 != chartWindow) dataWindow4->updateControlsSilently(maxPoints, newTime);
            if (dataWindow5 && dataWindow5 != chartWindow) dataWindow5->updateControlsSilently(maxPoints, newTime);
            if (dataWindow6 && dataWindow6 != chartWindow) dataWindow6->updateControlsSilently(maxPoints, newTime);
            if (multiChartWindow) multiChartWindow->updateControlsSilently(maxPoints, newTime);
        });
    }
    
    // 显示图表窗口
    chartWindow->show();
    // 确保窗口在最前面
    chartWindow->raise();
    chartWindow->activateWindow();
}

void MainWindow::showDataWindow(int windowIndex)
{
    // 根据通道号获取对应的窗口指针
    ChartWindow **windowPtr = nullptr;
    switch (windowIndex) {
    case 1: windowPtr = &dataWindow1; break;
    case 2: windowPtr = &dataWindow2; break;
    case 3: windowPtr = &dataWindow3; break;
    case 4: windowPtr = &dataWindow4; break;
    case 5: windowPtr = &dataWindow5; break;
    case 6: windowPtr = &dataWindow6; break;
    default: return;
    }
    
    // 如果窗口不存在，则创建它
        if (!(*windowPtr)) {
            *windowPtr = new ChartWindow(this);
            
            // 连接重置数据计数器的信号
            connect(*windowPtr, &ChartWindow::resetDataCounter, this, &MainWindow::resetDataCounter);
            
            // 设置窗口标题
            (*windowPtr)->setWindowTitle(windowTitles[windowIndex - 1]);
        
        // 设置最大数据点数量和采样时间
        (*windowPtr)->setMaxPoints(maxPoints);
        (*windowPtr)->setSampleTime(ui->sampleTimeEdit->text().toInt());
        
        // 由于我们已经移除了主界面图表，所以不需要从主界面同步数据
        // 新窗口将从创建后开始接收新的数据点
        
        // 当窗口关闭时释放资源
        connect(*windowPtr, &QMainWindow::destroyed, [this, windowIndex]() {
            switch (windowIndex) {
            case 1: dataWindow1 = nullptr; break;
            case 2: dataWindow2 = nullptr; break;
            case 3: dataWindow3 = nullptr; break;
            case 4: dataWindow4 = nullptr; break;
            case 5: dataWindow5 = nullptr; break;
            case 6: dataWindow6 = nullptr; break;
            }
        });
        
        // 连接参数更改信号
        connect(*windowPtr, &ChartWindow::sampleSizeChanged, this, [this, windowPtr](qint64 newSize) {
            // 更新主窗口的maxPoints变量
            maxPoints = newSize;
            ui->sampleSizeEdit->setText(QString::number(newSize));
            ui->sampleSizeLabel->setText(QString::number(newSize));
            
            // 更新其他所有窗口的采样点数量
            if (chartWindow) chartWindow->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
            if (dataWindow1 && dataWindow1 != *windowPtr) dataWindow1->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
            if (dataWindow2 && dataWindow2 != *windowPtr) dataWindow2->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
            if (dataWindow3 && dataWindow3 != *windowPtr) dataWindow3->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
            if (dataWindow4 && dataWindow4 != *windowPtr) dataWindow4->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
            if (dataWindow5 && dataWindow5 != *windowPtr) dataWindow5->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
            if (dataWindow6 && dataWindow6 != *windowPtr) dataWindow6->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
            if (multiChartWindow) multiChartWindow->updateControlsSilently(newSize, ui->sampleTimeEdit->text().toInt());
        });
        
        connect(*windowPtr, &ChartWindow::sampleTimeChanged, this, [this, windowPtr](int newTime) {
            // 更新主窗口的采样时间
            ui->sampleTimeEdit->setText(QString::number(newTime));
            ui->sampleTimeLabel->setText(QString::number(newTime) + " ms");
            
            // 更新其他所有窗口的采样时间
            if (chartWindow) chartWindow->updateControlsSilently(maxPoints, newTime);
            if (dataWindow1 && dataWindow1 != *windowPtr) dataWindow1->updateControlsSilently(maxPoints, newTime);
            if (dataWindow2 && dataWindow2 != *windowPtr) dataWindow2->updateControlsSilently(maxPoints, newTime);
            if (dataWindow3 && dataWindow3 != *windowPtr) dataWindow3->updateControlsSilently(maxPoints, newTime);
            if (dataWindow4 && dataWindow4 != *windowPtr) dataWindow4->updateControlsSilently(maxPoints, newTime);
            if (dataWindow5 && dataWindow5 != *windowPtr) dataWindow5->updateControlsSilently(maxPoints, newTime);
            if (dataWindow6 && dataWindow6 != *windowPtr) dataWindow6->updateControlsSilently(maxPoints, newTime);
            if (multiChartWindow) multiChartWindow->updateControlsSilently(maxPoints, newTime);
        });
    }
    
    // 显示图表窗口
    (*windowPtr)->show();
    // 确保窗口在最前面
    (*windowPtr)->raise();
    (*windowPtr)->activateWindow();
}

void MainWindow::on_saveDataButton_clicked()
{
    if (!isSavingData) {
        // 检查是否处于暂停状态
        if (isPaused) {
            QMessageBox::warning(this, "提示", "在暂停状态下无法开始保存数据，请先点击\"继续\"按钮。");
            return;
        }
        
        // 打开文件对话框选择保存位置
        QString fileName = QFileDialog::getSaveFileName(this, "保存数据", 
            QDateTime::currentDateTime().toString("yyyy-MM-dd_HH-mm-ss"), "CSV文件 (*.csv);;所有文件 (*.*)");
        
        if (fileName.isEmpty())
            return;
        
        // 创建文件
        dataFile = new QFile(fileName);
        if (!dataFile->open(QIODevice::WriteOnly | QIODevice::Text)) {
            QMessageBox::warning(this, "错误", "无法打开文件进行写入:");
            delete dataFile;
            dataFile = nullptr;
            return;
        }
        
        // 创建文本流并设置UTF-8编码
        dataStream = new QTextStream(dataFile);
        #if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0)
        dataStream->setEncoding(QStringConverter::Utf8);
        #else
        dataStream->setCodec("UTF-8");
        #endif
        // 写入UTF-8 BOM (字节顺序标记)，确保Excel等程序能正确识别编码
        *dataStream << "\xEF\xBB\xBF";
        
        // 写入表头
        *dataStream << "时间戳,通道1,通道2,通道3,通道4,通道5,通道6\n";
        
        // 更新UI状态
        isSavingData = true;
        saveDataButton->setText("停止保存数据");
        
        // 记录开始时间
        startTime = QDateTime::currentDateTime();
        
        ui->statusBar->showMessage("数据保存已开始: " + fileName);
    } else {
        // 停止保存数据
        if (dataStream) {
            delete dataStream;
            dataStream = nullptr;
        }
        
        if (dataFile) {
            dataFile->close();
            delete dataFile;
            dataFile = nullptr;
        }
        
        // 更新UI状态
        isSavingData = false;
        saveDataButton->setText("开始保存数据");
        
        ui->statusBar->showMessage("数据保存已停止");
    }
}

void MainWindow::updateTimeAxis()
{
    // 检查串口是否打开、是否应该自动滚动时间轴以及是否处于暂停状态
    if (!serial->isOpen() || !timeAxisAutoScroll || isPaused) {
        return;
    }
}

void MainWindow::on_pauseButton_clicked()
{
    // 切换暂停状态
    isPaused = !isPaused;
    
    // 更新按钮文本和状态栏消息
    if (isPaused) {
        ui->pauseButton->setText("继续");
        ui->statusBar->showMessage("曲线显示已暂停");
    } else {
        ui->pauseButton->setText("暂停");
        ui->statusBar->showMessage("曲线显示已继续");
    }
    
    // 获取当前时间
    int currentTime = QDateTime::currentMSecsSinceEpoch();
    
    // 检查是否超过一定时间没有收到新数据（这里设置为100ms）
    if (currentTime - lastDataUpdateTime > 100) {
        // 增加数据计数器，确保持续递增
        dataCounter++;
        
        // 获取当前时间作为新的数据点时间
        QDateTime currentDateTime = QDateTime::currentDateTime();
        qreal xValue = currentDateTime.toMSecsSinceEpoch();
        
        // 记录开始时间（如果还没有记录）
        if (startTime.isNull()) {
            startTime = currentDateTime;
        }
        
        // 由于我们已经移除了主界面图表，所以不需要添加0值数据点到主界面图表
        // 多图表整合窗口会在resetDataCounter信号中处理数据重置
        
        // 更新扩展图表窗口中的时间轴
        if (chartWindow) {
            chartWindow->updateTimeAxisWithoutData();
        }
        
        // 更新各个数据通道窗口的时间轴
        if (dataWindow1) dataWindow1->updateTimeAxisWithoutData();
        if (dataWindow2) dataWindow2->updateTimeAxisWithoutData();
        if (dataWindow3) dataWindow3->updateTimeAxisWithoutData();
        if (dataWindow4) dataWindow4->updateTimeAxisWithoutData();
        if (dataWindow5) dataWindow5->updateTimeAxisWithoutData();
        if (dataWindow6) dataWindow6->updateTimeAxisWithoutData();
        
        // 更新多图表整合窗口的时间轴
        if (multiChartWindow) {
            multiChartWindow->updateTimeAxisWithoutData();
        }
    }
}

void MainWindow::closeEvent(QCloseEvent *event)
{
    // 确保在关闭窗口前关闭数据文件
    if (isSavingData) {
        if (dataStream) {
            delete dataStream;
            dataStream = nullptr;
        }
        
        if (dataFile) {
            dataFile->close();
            delete dataFile;
            dataFile = nullptr;
        }
    }
    
    savePortSettings();
    QMainWindow::closeEvent(event);
}
